# !/usr/bin/python
# @author: 'hobby'
# @datetime: 2023-02-27 11:36
# @desc:  snmp获取交换机信息


# pip install pysnmp

import threading
import logging
from pysnmp.hlapi import *

from system_config import SysCfg

_logger = logging.getLogger(__name__)


# snmp_version = '2c'
# # H3C 交换机的 IP 地址
# device_ip = '10.34.2.254'
# # H3C 交换机的 SNMP 社区字符串
# community_string = 'h3c'
# OID（对象标识符），表示 H3C 交换机的设备名称


def synchronized(func):
    func.__lock__ = threading.Lock()

    def lock_func(*args, **kwargs):
        with func.__lock__:
            return func(*args, **kwargs)

    return lock_func


class metaclass(type):
    def __init__(cls, *args, **kwargs):
        cls.__instance = None
        super().__init__(*args, **kwargs)

    @synchronized
    def __call__(cls, *args, **kwargs):
        if not cls.__instance:
            cls.__instance = super().__call__(*args, **kwargs)
        return cls.__instance


class ApiHelper_Sbmp(metaclass=metaclass):
    """
    硬件信息获取
    """

    def __init__(self):
        self.snmp_version = SysCfg.c("snmp.snmp_version", str, '2c')
        self.device_ip = SysCfg.c("snmp.device_ip", str, '10.34.2.254')
        self.community_string = SysCfg.c("snmp.community_string", str, 'h3c')

    def get_result(self, device_name_oid):
        """
        获取结果
        """
        _logger.info("开始获取snmp数据")
        errorIndication, errorStatus, errorIndex, varBinds = next(
            getCmd(SnmpEngine(),
                   CommunityData(self.community_string, mpModel=0),
                   UdpTransportTarget((self.device_ip, 161)),
                   ContextData(),
                   ObjectType(ObjectIdentity(device_name_oid)))
        )
        if errorIndication:
            raise Exception(errorIndication)
        elif errorStatus:
            raise Exception('%s at %s' % (errorStatus.prettyPrint(),
                                          errorIndex and varBinds[int(errorIndex) - 1][0] or '?'))
        else:
            result_list = []
            for varBind in varBinds:
                result_list.extend([{x: x.prettyPrint()} for x in varBind])
            return result_list

# if __name__ == '__main__':
# 事例
# device_name_oid = '1.3.6.1.2.1.47.1.1.1.1.12.1'  # 设备型号
# device_name_oid = '1.3.6.1.4.1.25506.2.6.1.1.1.1.10.3'  # CPU 使用率
# a = ApiHelper_Sbmp()
# a.get_result(device_name_oid)
